package ginplus

import (
	"gitee.com/hongzhaomin/hzm-common-go/coll"
	"gitee.com/hongzhaomin/hzm-common-go/strutil"
	"net/http"
)

type MappingHandlerProcessor interface {
	Before(mapping *HandlerMappingWrapper) bool
	After(mapping *HandlerMappingWrapper, result any) bool
}

const (
	permissionsTag = "perms"       // 权限tag，支持整个controller类和属性
	accessToken    = "accessToken" // 请求token变量名
	noAuth         = "noauth"      // Tag的value项，Permission的固定选项值
)

func NewDefaultProcessor(httpSession HttpSession) *DefaultMappingHandlerProcessor {
	return &DefaultMappingHandlerProcessor{
		httpSession: httpSession,
	}
}

var _ MappingHandlerProcessor = (*DefaultMappingHandlerProcessor)(nil)

type DefaultMappingHandlerProcessor struct {
	httpSession HttpSession
}

func (my DefaultMappingHandlerProcessor) Before(mapping *HandlerMappingWrapper) bool {
	permissions := SpitCommaAndTrim(mapping.GetTag(permissionsTag))
	httpSession := my.httpSession
	if coll.Contains(permissions, noAuth) {
		return true
	}

	goLocal := GetUserGoroutineLocal()
	goLocal.Remove()
	token := my.getAccessToken(mapping)
	if strutil.IsBlank(token) {
		PrintErrPage(mapping.GetResponse(), http.StatusUnauthorized)
		return false
	}
	attr := httpSession.GetAttribute(token)
	if attr == nil {
		PrintErrPage(mapping.GetResponse(), http.StatusUnauthorized)
		return false
	}
	goLocal.Set(attr)
	return true
}

func (my DefaultMappingHandlerProcessor) After(_ *HandlerMappingWrapper, _ any) bool {
	GetUserGoroutineLocal().Remove()
	return true
}

func (my DefaultMappingHandlerProcessor) getAccessToken(mapping *HandlerMappingWrapper) string {
	// 先从路径中获取token
	token := mapping.QueryParam(accessToken)
	if strutil.IsBlank(token) {
		// 未获取到，再从header中获取
		token = mapping.GetHeader(accessToken)
	}
	if strutil.IsBlank(token) {
		// 还未获取到，最后从cookie中获取
		if cookie, err := mapping.Cookie(accessToken); err == nil {
			// fixme 这个从cookie中获取的方式有待测试
			token = cookie
		}
	}
	return token
}
